﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

/// <summary>
/// 玩家指令记录基类
/// </summary>
public abstract class PlayerCommandRecordCompoent:ECSCompoentBase
{
    /// <summary>
    /// 玩家指令(未有最后确认帧时取该数据预测《本地》/默认)
    /// </summary>
    public PlayerCommandBase Input;
    /// <summary>
    /// 玩家指令字典(哪一帧，指令)
    /// </summary>
    public Dictionary<int,PlayerCommandBase> inputCache
        =new Dictionary<int, PlayerCommandBase>();
    /// <summary>
    /// 指定确认字典
    /// </summary>
    public Dictionary<int,bool> ConfirmCache
        =new Dictionary<int, bool>();
    /// <summary>
    /// 指令是否一致
    /// </summary>
    public bool IsConfirm;
    /// <summary>
    /// 最后输入帧（以确认）,进行预测时取该帧数据
    /// </summary>
    public int LastInputFrame = -1;
    /// <summary>
    /// 获取指定帧的玩家指令
    /// </summary>
    /// <param name="frame"></param>
    /// <returns></returns>
    public PlayerCommandBase GetInputCache(int frame)
    {
        if (inputCache.ContainsKey(frame))
        {
            return inputCache[frame];
        }

        return null;
    }
    //预测指令
    private PlayerCommandBase foreast;
    /// <summary>
    /// 获取预测输入指令
    /// </summary>
    /// <param name="frame"></param>
    /// <returns></returns>
    public PlayerCommandBase GetForeast(int frame)
    {
        //取出上一帧的缓存赋值给下一帧做预测用
         foreast = GetInputCache(LastInputFrame);
        if (foreast == null)
        {//没有则取默认值
            foreast = Input;
        }

        PlayerCommandBase cmd = foreast.DeepCopy();
        foreast = null;
        cmd.frame = frame;
        cmd.id = Entity.ID;
        return cmd;
    }

    private int cmdFrame;
    /// <summary>
    /// 记录玩家指令
    /// </summary>
    /// <param name="cmd"></param>
    public void RecordCommand(PlayerCommandBase cmd)
    {
        cmdFrame = cmd.frame;

        if (inputCache.ContainsKey(cmdFrame))
        {
            inputCache[cmdFrame] = cmd;
        }
        else
        {
            inputCache.Add(cmdFrame,cmd);
        }
    }
    /// <summary>
    /// 清除指定帧之前的记录
    /// </summary>
    /// <param name="frame"></param>
    public void ClearCacheBefore(int frame)
    {
        for (int i = 0,j=inputCache.Count; i < j; i++)
        {
            if (inputCache[i].frame<frame)
            {
                inputCache.Remove(i);
                i--;
                j--;
            }
        }

    }
    /// <summary>
    /// 设置冲突
    /// </summary>
    /// <param name="frame"></param>
    /// <param name="isMyConfirm"></param>
    public void SetConflict(int frame, bool isMyConfirm)
    {
        if (ConfirmCache.ContainsKey(frame))
        {
            if (isMyConfirm)
            {
                ConfirmCache[frame] = isMyConfirm;
            }
        }
        else
        {
            ConfirmCache.Add(frame,isMyConfirm);
        }
    }
    /// <summary>
    /// 指令是否冲突
    /// </summary>
    /// <param name="frame"></param>
    /// <returns></returns>
    public bool GetConflict(int frame)
    {
        if (ConfirmCache.ContainsKey(frame))
        {
            return ConfirmCache[frame];
        }
        else
        {
            return false;
        }
    }
    /// <summary>
    /// 第几帧消息是否已经确认是否冲突（预测与实际）
    /// </summary>
    /// <param name="frame"></param>
    /// <returns></returns>

    public bool GetAllMessage(int frame)
    {
        if (ConfirmCache.ContainsKey(frame))
        {
            return true;
        }
        else
        {
            return false;
        }
    }
}

